
package com.jf.cloud.multishop.controller.admin;

import com.jf.cloud.api.auth.constant.SysTypeEnum;
import com.jf.cloud.common.constant.Constant;
import com.jf.cloud.common.constant.StatusEnum;
import com.jf.cloud.common.database.dto.PageDTO;
import com.jf.cloud.common.database.vo.PageVO;
import com.jf.cloud.common.exception.LuckException;
import com.jf.cloud.common.response.ResponseEnum;
import com.jf.cloud.common.response.ServerResponseEntity;
import com.jf.cloud.common.security.AuthUserContext;
import com.jf.cloud.multishop.constant.NoticeType;
import com.jf.cloud.multishop.dto.NoticeDTO;
import com.jf.cloud.multishop.model.Notice;
import com.jf.cloud.multishop.service.NoticeService;
import com.jf.cloud.multishop.vo.NoticeVO;
import io.swagger.v3.oas.annotations.tags.Tag;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.Operation;
import ma.glasnost.orika.MapperFacade;
import org.springdoc.api.annotations.ParameterObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import javax.validation.Valid;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;

/**
 * 公告
 * @author zz
 * @date 2020-11-25 17:57:56
 */
@RestController("adminNoticeController")
@RequestMapping("/mp/notice")
@Tag(name = "admin-公告")
public class NoticeController {

    @Autowired
    private NoticeService noticeService;

    @Autowired
    private MapperFacade mapperFacade;

    @GetMapping("/page")
    @Operation(summary = "获取公告列表" , description = "分页获取公告列表")
    public ServerResponseEntity<PageVO<NoticeVO>> page(@Valid PageDTO pageDTO, @ParameterObject NoticeDTO noticeDTO) {
        noticeDTO.setShopId(AuthUserContext.get().getTenantId());
        noticeDTO.setAccountId(AuthUserContext.get().getTenantId());
        PageVO<NoticeVO> noticePage = noticeService.page(pageDTO, noticeDTO);
        return ServerResponseEntity.success(noticePage);
    }

    @GetMapping("/p/page")
    @Operation(summary = "获取平台公告列表（商家端或供应商端）" , description = "获取平台公告列表（商家端或供应商端）")
    public ServerResponseEntity<List<NoticeVO>> list() {
        List<NoticeVO> notices = noticeService.getlistByShopId(Constant.PLATFORM_SHOP_ID, NoticeType.TO_MULTISHOP.value());
        //筛选出立即发送和到时间定时发送的公告
        List<NoticeVO> list = notices.stream().filter(noticeVO -> Objects.equals(noticeVO.getImmediatelySend(), 1) || (Objects.equals(noticeVO.getImmediatelySend(), 0) && noticeVO.getSendTime().before(new Date()))).collect(Collectors.toList());
        return ServerResponseEntity.success(list);
    }

    @GetMapping("/p/pagePlatformNotice")
    @Operation(summary = "获取平台公告分页列表（商家端或供应商端）" , description = "获取平台公告分页列表（商家端或供应商端）")
    public ServerResponseEntity<PageVO<NoticeVO>> pagePlatformNotice(@Valid PageDTO pageDTO, @ParameterObject NoticeDTO noticeDTO) {
        Integer sysType = AuthUserContext.get().getSysType();
        noticeDTO.setShopId(Constant.PLATFORM_SHOP_ID);
        noticeDTO.setType(Objects.equals(sysType, SysTypeEnum.MULTISHOP.value()) ?  NoticeType.TO_MULTISHOP.value() : NoticeType.TO_SUPPLIER.value());
        noticeDTO.setAccountId(AuthUserContext.get().getTenantId());
        noticeDTO.setSendTime(new Date());
        noticeDTO.setStatus(StatusEnum.ENABLE.value());
        PageVO<NoticeVO> notices = new PageVO<>();
        notices = noticeService.pagePlatformNotice(pageDTO,  noticeDTO);

        return ServerResponseEntity.success(notices);
    }

    @GetMapping
    @Operation(summary = "获取公告" , description = "根据id获取公告")
    public ServerResponseEntity<NoticeVO> getById(@ParameterObject @RequestParam Long id) {
        return ServerResponseEntity.success(noticeService.getById(id));
    }

    @PostMapping
    @Operation(summary = "保存公告" , description = "保存公告")
    public ServerResponseEntity<Void> save(@Valid @RequestBody NoticeDTO noticeDTO) {
        Notice notice = mapperFacade.map(noticeDTO, Notice.class);
        Long shopId = AuthUserContext.get().getTenantId();
        //商家端创建公告
        if(!Objects.equals(shopId, Constant.PLATFORM_SHOP_ID)){
            notice.setTypes(NoticeType.TO_USER.value().toString());
            notice.setImmediatelySend(1);
        }
        notice.setShopId(shopId);
        noticeService.save(notice);
        noticeService.removeCacheByShopIdAndType(shopId, NoticeType.TO_USER.value());
        List<Integer> typeList = Arrays.stream(notice.getTypes().split(",")).map(s -> Integer.parseInt(s.trim())).collect(Collectors.toList());
        for ( Integer type : typeList) {
            noticeService.removeCacheByShopIdAndType(shopId, type);
        }

        return ServerResponseEntity.success();
    }

    @PutMapping
    @Operation(summary = "更新公告" , description = "更新公告")
    public ServerResponseEntity<Void> update(@Valid @RequestBody NoticeDTO noticeDTO) {
        Notice notice = mapperFacade.map(noticeDTO, Notice.class);
        Long shopId = AuthUserContext.get().getTenantId();
        NoticeVO dbNotice = noticeService.getById(notice.getId());
        if (!Objects.equals(dbNotice.getShopId(), AuthUserContext.get().getTenantId())) {
            throw new LuckException(ResponseEnum.UNAUTHORIZED);
        }
        boolean isPublish = Objects.equals(dbNotice.getStatus(), StatusEnum.DISABLE.value()) && Objects.equals(notice.getStatus(), StatusEnum.ENABLE.value());
        if(isPublish) {
            notice.setPublishTime(new Date());
        } else {
            notice.setPublishTime(null);
        }

        noticeService.update(notice);
        List<Integer> typeList = Arrays.stream(notice.getTypes().split(",")).map(s -> Integer.parseInt(s.trim())).collect(Collectors.toList());
        for ( Integer type : typeList) {
            noticeService.removeCacheByShopIdAndType(shopId, type);
        }
        return ServerResponseEntity.success();
    }

    @DeleteMapping
    @Operation(summary = "删除公告" , description = "根据公告id删除公告")
    @Parameter(name = "id", description = "公告id" , required = true)
    public ServerResponseEntity<Void> delete(@RequestParam("id") Long id) {
        NoticeVO dbNotice = noticeService.getById(id);
        Long shopId = AuthUserContext.get().getTenantId();
        if (Objects.isNull(dbNotice)) {
            return ServerResponseEntity.success();
        } else if (!Objects.equals(dbNotice.getShopId(), shopId)) {
            throw new LuckException(ResponseEnum.UNAUTHORIZED);
        }
        noticeService.deleteById(id);
        List<Integer> typeList = Arrays.stream(dbNotice.getTypes().split(",")).map(s -> Integer.parseInt(s.trim())).collect(Collectors.toList());
        for ( Integer type : typeList) {
            noticeService.removeCacheByShopIdAndType(shopId, type);
        }
        return ServerResponseEntity.success();
    }
}
